﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Linq.Expressions;
using ZWGBlog.Specification;
using ZWQBlog.Model;
using ZWQBlog.Repository;
using ZWQBlog.Repository.Contract;

namespace ZWGBlog.Repository
{
    public class RepositoryBase<TEntity> : IRepository<TEntity, PageData<TEntity>> where TEntity : class, new()
    {
        public ZWQBlogContext Context;

        public RepositoryBase(IUnitOfWork unitOfWork)
        {
            Context = unitOfWork as ZWQBlogContext;
        }

        #region IRepository<TEntity,PageData<TEntity>> Members

        public IList<TEntity> FindAll()
        {
            return Context.CreateObjectSet<TEntity>().ToList();
        }

        public PageData<TEntity> FindAll<TOrderBy>(int pageIndex, int pageSize, ISpecification<TEntity> where,
                                                           Expression<Func<TEntity, TOrderBy>> orderBy, bool isDesc)
        {
            IOrderedQueryable<TEntity> query = isDesc
                                                   ? (Context.CreateObjectSet<TEntity>()).Where(where.SatisfiedBy()).
                                                         OrderByDescending(orderBy)
                                                   : (Context.CreateObjectSet<TEntity>()).Where(where.SatisfiedBy()).
                                                         OrderBy(orderBy);

            var pageData = new PageData<TEntity>();
            pageData.TotalCount = query.Count();
            pageData.DataList = query.Skip((pageIndex - 1)*pageSize).Take(pageSize).ToList();

            return pageData;
        }

        public TEntity Find(ISpecification<TEntity> where)
        {
            return (Context.CreateObjectSet<TEntity>()).Where(where.SatisfiedBy()).FirstOrDefault();
        }

        public void Add(TEntity entity)
        {
            if (entity != null)
                (Context.CreateObjectSet<TEntity>()).AddObject(entity);
        }

        public void Delete(TEntity entity)
        {
            if (entity != null)
                Context.DeleteObject(entity);
        }

        public void Update(TEntity entity)
        {
            //.Net 3.5支持的方法
            //EntityKey key = context.CreateEntityKey("BlogArticle", model);
            //object orgData;
            //if (context.TryGetObjectByKey(key, out orgData))
            //{
            //    context.ApplyPropertyChanges(key.EntitySetName, model);
            //    context.SaveChanges();
            //    return true;
            //}
            //return false;

            //.Net 4.0支持的方法
            EntityKey key = Context.CreateEntityKey((Context.CreateObjectSet<TEntity>()).EntitySet.Name, entity);
            object orgEntity;
            if (Context.TryGetObjectByKey(key, out orgEntity))
            {
                Context.ApplyCurrentValues(key.EntitySetName, entity);
            }
        }

        #endregion
    }
}